﻿using SharepointCommon.Attributes;
using System;
using System.Collections.Generic;
using System.Globalization;
using System.Linq;
using System.Reflection;
using System.Text;

namespace Uportal.Shp.Core.Common
{
    /// <summary>
    /// Enum to string: http://stackoverflow.com/questions/424366/c-sharp-string-enums
    /// </summary>
    public static class EnumResolver
    {
        public static string GetStringValue(IConvertible value)
        {
            Type type = value.GetType();
            if (!type.IsEnum)
            {
                throw new ArgumentException("value must be an enumerated type");
            }

            FieldInfo fi = type.GetField(value.ToString(CultureInfo.InvariantCulture));
            var attrs = fi.GetCustomAttributes(typeof(FieldAttribute), false) as FieldAttribute[];
            if (attrs != null && attrs.Length > 0)
            {
                return attrs[0].Name;
            }

            throw new Exception(string.Format("Enum value not found. Enum type: {0}, passed value: {1}", type, value));
        }

        public static T GetEnumValue<T>(string value) where T : struct, IConvertible
        {
            if (!typeof(T).IsEnum)
            {
                throw new ArgumentException("T must be an enumerated type");
            }

            foreach (T item in Enum.GetValues(typeof(T)))
            {
                FieldInfo fi = typeof(T).GetField(item.ToString(CultureInfo.InvariantCulture));
                var attrs = fi.GetCustomAttributes(typeof(FieldAttribute), false) as FieldAttribute[];

                if (attrs != null && attrs.Length > 0 && attrs[0].Name == value)
                    return item;
            }

            throw new Exception(string.Format("Enum value not found. Enum type: {0}, passed value: {1}", typeof(T), value));
        }

        public static IEnumerable<string> GetStringValues<T>() where T : struct, IConvertible
        {
            return Enum.GetValues(typeof(T)).Cast<T>().Select(x => GetStringValue(x));
        }
    }
}
